﻿using System;
using System.Text;
using System.Ext.Xml;
using System.Xml;
using System.Reflection;

namespace mfXmlSerializer
{
    /// <summary>
    /// represents the serialization strategy for enum-values
    /// </summary>
    public class mfMapEnumElement : mfMapBaseElement
    {     
        #region CTOR

        public mfMapEnumElement(mfMapBaseElement baseElement)
            : base(baseElement.Name, baseElement.SetMethod, baseElement.GetMethod, baseElement.ChildMap)
        { }

        #endregion

        #region Methods

        protected override void SerializeElement(XmlWriter xmlWriter, object source)
        {
            //get value on target            
            Object enumValue = GetMethod.Invoke(source, null);
            //enumValueString (.NET)    = 'Debug'
            //enumValueString (.NETMF)  = '1' 
            var enumValueString = enumValue.ToString();
            if (!enumValueString.IsNumber())//.NET runtime environment specilized case (string serilized enum value)
            {
                //the first Field in enums are named as 'value__', alias Enumb.GetValue(...)
                enumValueString = ElementType.GetFields()[0].GetValue(enumValue).ToString();
            }
            xmlWriter.WriteElementStringIfNotNull(Name, enumValueString);
        }

        protected override void DeserializeElement(XmlReader xmlReader, object target)
        {
            xmlReader.Read();
            if (xmlReader.IsNotNodeTextType(this)) return;
            var enumValue = xmlReader.Value.DeserializeEnumAsStringNumber();
            SetElement(xmlReader, target, enumValue);
        }

        protected override void ExecuteSetElement(object target, string newValue)
        {
            var enumValue = newValue.DeserializeEnumAsStringNumber();
            SetMethod.Invoke(target, new object[] { enumValue });
        }


        #endregion
    }
}
